package com.hruiworks.campusgroup.service.impl;

import com.hruiworks.campusgroup.enums.ErrorCode;
import com.hruiworks.campusgroup.exception.BusinessException;
import com.hruiworks.campusgroup.quartz.factory.trigger.TriggerFactory;
import com.hruiworks.campusgroup.quartz.listener.GlobalJobListener;
import com.hruiworks.campusgroup.service.ScheduledJobService;
import lombok.extern.slf4j.Slf4j;
import org.quartz.*;
import org.quartz.impl.StdSchedulerFactory;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.Objects;

import static org.quartz.CronScheduleBuilder.cronSchedule;
import static org.quartz.JobBuilder.newJob;
import static org.quartz.TriggerBuilder.newTrigger;

@Service
@Slf4j
public class ScheduledJobServiceServiceImpl implements ScheduledJobService {

    /**
     * 任务调度器
     */
    private final static Scheduler scheduler;

    // 初始化调度器
    static {
        StdSchedulerFactory stdSchedulerFactory = new StdSchedulerFactory();
        try {
            scheduler = stdSchedulerFactory.getScheduler();
            // 注册全局任务监听器
            GlobalJobListener globalJobListener = new GlobalJobListener();
            scheduler.getListenerManager().addJobListener(globalJobListener);
            scheduler.start();
        } catch (SchedulerException e) {
            throw new BusinessException(ErrorCode.OTHER_ERROR, "任务调度器初始化失败");
        }

    }

    @Override
    public Scheduler getScheduler() {
        return scheduler;
    }

    @Override
    public void registerJob(JobDetail jobDetail, Trigger trigger) {
        try {
            scheduler.scheduleJob(jobDetail, trigger);
        } catch (SchedulerException e) {
            if (e.getMessage().startsWith("Based on configured schedule, the given trigger '")) {
                try {
                    // 删除触发器
                    scheduler.unscheduleJob(trigger.getKey());
                    // 删除任务
                    scheduler.deleteJob(jobDetail.getKey());
                } catch (Exception exception) {
                    log.error("该触发器时间/任务不合理且不存在，不做过多的操作");
                }
            }
        }
    }

    @Override
    public <T extends Job> void registerJob(Class<T> jobClass, String jobName, String jobGroup, String triggerName, String triggerGroup, String cron) {

        JobDetail jobDetail = newJob(jobClass).withIdentity(jobName, jobGroup).build();
        CronTrigger trigger = newTrigger()
                .withIdentity(triggerName, triggerGroup)
                .withSchedule(cronSchedule(cron))
                .build();
        registerJob(jobDetail, trigger);
    }

    @Override
    public void changeJobTriggerTime(String triggerName, String triggerGroup, String cron) {
        TriggerFactory triggerFactory = new TriggerFactory();
        Trigger trigger = triggerFactory.getTrigger(triggerGroup, triggerName, cron);
        try {
            Date date = scheduler.rescheduleJob(trigger.getKey(), trigger);
            if (Objects.isNull(date)) {
                log.error("时间修改失败，可能是由于是设置的时间已经超过");
            }
        } catch (SchedulerException e) {
            log.error("时间修改失败，可能是由于是设置的时间已经超过: "+e.getMessage());
        }

    }


}
